package com.naiterui.ehp.bs.im.network.transcode.coders;

import org.slf4j.Logger;

import com.alibaba.fastjson.JSON;
import org.slf4j.LoggerFactory;
import com.naiterui.ehp.bs.im.exception.NaiteruiIMException;
import com.naiterui.ehp.bs.im.exception.ExceptionCodes;
import com.naiterui.ehp.bs.im.network.protocl.Message;

/**
 * 消息编码与解码的抽象类
 * 用于IM信息的编码与解码
 * 此类中定义了将资源信息转换为JAVA对象的方法
 * 根据消息类型的不同，不同的消息将使用不同的编解器
 * 这为以后的消息类型的扩展提供了较好的扩展性
 * <P>File name : AbstractTransCoder.java </P>
 * <P>Author : zhouyanxin </P>
 * <P>Date : 2015年6月22日 </P>
 */
public abstract class AbstractTransCoder<T> {

    /**
     * LOGGER
     */
    private static final Logger LOGGER = LoggerFactory.getLogger(AbstractTransCoder.class);

    /**
     * 消息序列化
     * AbstractTransCoder.toMessageString()<BR>
     * <P>Author : zhouyanxin </P>
     * <P>Date : 2015年6月23日 </P>
     * @param message
     * @return
     * @throws NaiteruiIMException
     */
    public String serializeMessage(Message<?> message) throws NaiteruiIMException {
        return JSON.toJSONString(message);
    }

    /**
     * 消息反序列化
     * AbstractTransCoder.toMessageObject()<BR>
     * <P>Author : zhouyanxin </P>
     * <P>Date : 2015年6月22日 </P>
     * @param message
     * @return
     */
    @SuppressWarnings({ "rawtypes", "unchecked" })
    public Message deserializeMessage(String message) throws NaiteruiIMException {

        // 解析消息类型
        Message messageBean = null;
        try {
            messageBean = JSON.toJavaObject(JSON.parseObject(message), Message.class);
        } catch (Exception e) {
            LOGGER.error("message is not a available json format! message is {}", message, e);
            throw new NaiteruiIMException(ExceptionCodes.MSG_FORMAT_INVALID);
        }

        // 反序列化消息中的内容属性信息
        T t = this.deserializeMessageContent(messageBean.getContent().toString());
        messageBean.setContent(t);

        return messageBean;
    }

    /**
     * 反序列化消息中的内容属性信息
     * AbstractTransCoder.deserializeMessageContent()
     * @Author zhouyanxin
     * @Date 2016年4月12日
     * @since 1.0.0
     * @param content
     * @return
     * @throws NaiteruiIMException
     */
    protected abstract T deserializeMessageContent(String content) throws NaiteruiIMException;
}
